package com.hxwm.hwdbtool.controller;

import com.hxwm.hwdbtool.controller.dialog.BaseDBConnectDialog;
import com.hxwm.hwdbtool.core.DatabaseConnectionListener;
import com.hxwm.hwdbtool.entity.dbconnect.*;
import com.hxwm.hwdbtool.util.DataSourceMetaDataUtil;
import com.hxwm.hwdbtool.util.HwUtil;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader;
import javafx.scene.Node;
import javafx.scene.Parent;
import javafx.scene.control.*;
import javafx.scene.layout.Pane;
import org.apache.log4j.Logger;

import java.io.IOException;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @program: hwdbtool
 * @ClassName GenerateMapper
 * @description:
 * @author: hxwm
 * @create: 2024-05-23 22:06
 * @Version 1.0
 **/
public class GenerateMapperController implements DatabaseConnectionListener {
    Logger logger = Logger.getLogger(GenerateMapperController.class);
    @FXML
    private Pane generateMapperPane;
    @FXML
    private ComboBox oldDataSourceComboBox;
    @FXML
    private ComboBox oldDataSourceDBComboBox;
    @FXML
    private ComboBox oldDataSourceTableComboBox;
    @FXML
    private Button addOldDataSourceBtn;
    @FXML
    private Button addOldTableBtn;
    @FXML
    private ComboBox newDataSourceComboBox;
    @FXML
    private Button addNewDataSourceBtn;
    @FXML
    private TableView oldDBTableView;

    private String listenerType;
    private HwDateSource newDateSource;
    private ObservableList<String> oldDataSourceOptions;
    private Map<String,HwConnection> oldDBHwconnections;
    public void initialize() {
        // 初始化操作，可以在这里添加事件监听器等
        oldDataSourceOptions = FXCollections.observableArrayList();
        oldDBHwconnections= new HashMap<>();
        oldDataSourceComboBox.setItems(oldDataSourceOptions);

        addOldDataSourceBtn.setOnAction(e->{
            listenerType = "oldDataSourceListener";
            String value = (String) oldDataSourceComboBox.getValue();
            HwDateSource hwDateSource = null;
            if(!HwUtil.isNullOrEmpty(value)) {
                hwDateSource = oldDBHwconnections.get(value.substring(0, value.lastIndexOf("-"))).getHwDateSource();
            }
            showConnectDialog(hwDateSource);
        });
        oldDataSourceComboBox.valueProperty().addListener((observable, oldValue, newValue)->{
            if(newValue != null) {
                String value = (String) newValue;
                HwConnection hwConnection = oldDBHwconnections.get(value.substring(0, value.lastIndexOf("-")));
                List<HwDatabase> databaseList = hwConnection.getDatabaseList();
                //ObservableList<Object> databaseList = FXCollections.observableArrayList(hwConnection.getDatabaseList());
                for (HwDatabase hwDatabase : databaseList) {
                    oldDataSourceDBComboBox.getItems().add(hwDatabase.getDatabaseName());
                }
            }
        });
        oldDataSourceDBComboBox.valueProperty().addListener((observable, oldValue, newValue)->{
            if(newValue != null) {
                String dbName = (String) newValue;
                String dataSource = (String)oldDataSourceComboBox.getValue();
                HwConnection hwConnection = oldDBHwconnections.get(dataSource.substring(0, dataSource.lastIndexOf("-")));
                List<HwDatabase> databaseList = hwConnection.getDatabaseList();
                for (HwDatabase hwDatabase : databaseList) {
                    List<HwTable> tableList = hwDatabase.getTableList();
                    if(dbName.equals(hwDatabase.getDatabaseName())){
                        for (HwTable hwTable : tableList) {
                            oldDataSourceTableComboBox.getItems().add(hwTable.getTableName());
                        }
                        break;
                    }
                }
            }
        });
        oldDataSourceTableComboBox.valueProperty().addListener((observable, oldValue, newValue)->{
            if(newValue != null) {
                String dataSource = (String)oldDataSourceComboBox.getValue();
                String dbName = (String)oldDataSourceDBComboBox.getValue();
                String tableName = (String) newValue;

                HwConnection hwConnection = oldDBHwconnections.get(dataSource.substring(0, dataSource.lastIndexOf("-")));
                List<HwDatabase> databaseList = hwConnection.getDatabaseList();
                for (HwDatabase hwDatabase : databaseList) {
                    List<HwTable> tableList = hwDatabase.getTableList();
                    if(dbName.equals(hwDatabase.getDatabaseName())){
                        for (HwTable hwTable : tableList) {
                            if(tableName.equals(hwTable.getTableName())){
                                List<HwColumn> columnList = hwTable.getColumnList();
                                ObservableList<String> row = FXCollections.observableArrayList();
                                for (HwColumn hwColumn : columnList) {
                                    row.add(hwColumn.getColumnName());
                                    row.add(hwColumn.getColumnType());
                                    row.add("");
                                }
                                oldDBTableView.getItems().add(row);
                                break;
                            }
                        }
                        break;
                    }
                }
            }
        });
        addOldTableBtn.setOnAction(e->{
            Object value = oldDataSourceTableComboBox.getValue();

        });
        addNewDataSourceBtn.setOnAction(e->{
            listenerType = "newDataSourceListener";
            showConnectDialog(newDateSource);
        });

    }

    /**
     * 数据库连接弹框
     * @param hwDateSource
     */
    private void showConnectDialog(HwDateSource hwDateSource){
        // 处理数据库连接菜单事件
        try {
            FXMLLoader fxmlLoader = new FXMLLoader(getClass().getResource("/fxml/dbconnect/dbconnectdialog.fxml"));
            Parent dialogRoot = fxmlLoader.load();
            //设置监听器，监听对话框的确定按钮，传递数据源对象
            BaseDBConnectDialog dialogController = fxmlLoader.getController();
            dialogController.setListener(this); // 设置主页面控制器为监听器

            Dialog<ButtonType> dialog = new Dialog<>();
            dialog.setTitle("新建数据库连接");
            dialog.getDialogPane().getButtonTypes().addAll(ButtonType.CANCEL);
            Node sysCancelButton = dialog.getDialogPane().lookupButton(ButtonType.CANCEL);
            sysCancelButton.setVisible(false);

            dialog.getDialogPane().setContent(dialogRoot);
            // 设置Dialog的owner为main.fxml的窗口
            dialog.initOwner(generateMapperPane.getScene().getWindow());
            // 处理窗口关闭事件，点击右上角X按钮时触发
            dialog.setOnCloseRequest(event1 -> {
                dialog.close();
            });

            if(!HwUtil.isNullOrEmpty(hwDateSource)){
                dialogController.getDbIpTextField().setText(hwDateSource.getDbIp());
                dialogController.getDbPortTextField().setText(hwDateSource.getDbPort());
                dialogController.getDbTypeComboBox().setValue(hwDateSource.getDriverType());
                dialogController.getDbNameTextField().setText(hwDateSource.getDbName());
                dialogController.getDbUserTextField().setText(hwDateSource.getDbUser());
                dialogController.getDbPasswordField().setText(hwDateSource.getDbPassword());
            }
            dialog.show();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void onDatabaseConnected(HwDateSource hwDateSource) {
        if(!HwUtil.isNullOrEmpty(hwDateSource)){
            logger.info("添加数据源");
            if ("oldDataSourceListener".equals(listenerType)){
                logger.info("添加导出数据源");
                String dbName = hwDateSource.getDbName();
                String dbIp = hwDateSource.getDbIp();
                String dbUser = hwDateSource.getDbUser();
                String keyName = dbName + "-" + dbUser + "-" + dbIp;
                //数据库添加了dbname,此时判断是否已添加了数据源
                int indexOf = oldDataSourceOptions.indexOf(keyName);
                if(indexOf < 0){
                    oldDataSourceOptions.add(keyName);
                    HwConnection databaseConnectInfo = DataSourceMetaDataUtil.getDatabaseConnectInfo(hwDateSource);
                    oldDBHwconnections.put(dbName + "-" + dbUser,databaseConnectInfo);
                }
            }
            if ("newDataSourceListener".equals(listenerType)){
                newDateSource = hwDateSource;
            }
            logger.info("添加数据源成功");
        }
        if(!HwUtil.isNullOrEmpty(oldDBHwconnections)){
            oldDataSourceComboBox.setDisable(false);
        }
    }
}